package io.nick.reqenhance.filter;

import io.nick.reqenhance.entry.ParamEntry;
import io.nick.reqenhance.utils.JacksonUtils;
import org.apache.commons.lang3.StringUtils;

import javax.servlet.*;
import javax.servlet.annotation.WebFilter;
import javax.servlet.http.HttpServletRequest;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;

/**
 * @author Nick
 * @date 2019-08-11 13:30
 */
@WebFilter(filterName = "reqUrlFilter", urlPatterns = "/*")
public class ReqFilter implements Filter {
  @Override
  public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)
      throws IOException, ServletException {
    HttpServletRequest req = (HttpServletRequest) request;
    MuteRequestWrapper requestWrapper = new MuteRequestWrapper(req);
    String uri = trimContextPath(requestWrapper);
    ParamEntry paramEntry = parseJson(requestWrapper);
    String forwardUri = paramEntry.getName();
    if (StringUtils.isNotBlank(forwardUri)) {
      uri = uri + forwardUri;
      byte[] mute = JacksonUtils.obj2jsonIgnoreNull(paramEntry.getData()).getBytes();
      requestWrapper.muteBuffer(mute);
      requestWrapper.getRequestDispatcher(uri).forward(requestWrapper, response);
    } else {
      chain.doFilter(requestWrapper, response);
    }
  }

  private String trimContextPath(HttpServletRequest request) {
    String origin = request.getRequestURI();
    String contextPath = request.getServletContext().getContextPath();
    String ret = origin.substring(contextPath.length());
    return ret.lastIndexOf("/") == ret.length() - 1 ? ret : ret.concat("/");
  }

  private ParamEntry parseJson(HttpServletRequest request) throws IOException {
    String resStr;
    BufferedReader br = new BufferedReader(new InputStreamReader(request.getInputStream()));
    StringBuilder sb = new StringBuilder();
    String line;
    while ((line = br.readLine()) != null) {
      sb.append(line);
    }
    br.close();
    resStr = sb.toString();
    System.out.println(resStr);
    //    return JSONObject.parseObject(resStr, ParamEntry.class);
    return JacksonUtils.json2pojo(resStr, ParamEntry.class);
  }
}
